package co.gov.igac.observatorio.beans.propuesta;

import co.gov.igac.observatorio.entidades.propuesta.Propuesta;
import co.gov.igac.observatorio.beans.propuesta.util.JsfUtil;
import co.gov.igac.observatorio.beans.propuesta.util.PaginationHelper;
import co.gov.igac.observatorio.ejbs.propuesta.PropuestaFacade;

import co.gov.igac.observatorio.entidades.propuesta.Gruporesultado;
import co.gov.igac.observatorio.entidades.propuesta.Participante;
import co.gov.igac.observatorio.entidades.propuesta.Presupuesto;
import co.gov.igac.observatorio.entidades.propuesta.Resultado;
import co.gov.igac.observatorio.entidades.propuesta.Tiporesultado;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.ResourceBundle;
import javax.ejb.EJB;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.SessionScoped;
import javax.faces.component.UIComponent;
import javax.faces.context.FacesContext;
import javax.faces.convert.Converter;
import javax.faces.convert.FacesConverter;
import javax.faces.model.DataModel;
import javax.faces.model.ListDataModel;
import javax.faces.model.SelectItem;

@ManagedBean(name = "propuestaController")
@SessionScoped
public class PropuestaController implements Serializable {

    private Propuesta current;
    private DataModel items = null;
    @EJB
    private co.gov.igac.observatorio.ejbs.propuesta.PropuestaFacade ejbFacade;
    private PaginationHelper pagination;
    private int selectedItemIndex;
    private Map<Integer, List<Resultado>> resultadosMap;
    private Map<Integer, List<Presupuesto>> presupuestosMap;

    public PropuestaController() {
    }

    public Propuesta getSelected() {
        if (current == null) {
            current = new Propuesta();
            selectedItemIndex = -1;
        }
        return current;
    }

    private PropuestaFacade getFacade() {
        return ejbFacade;
    }

    public PaginationHelper getPagination() {
        if (pagination == null) {
            pagination = new PaginationHelper(10) {

                @Override
                public int getItemsCount() {
                    return getFacade().count();
                }

                @Override
                public DataModel createPageDataModel() {
                    return new ListDataModel(getFacade().findRange(new int[]{getPageFirstItem(), getPageFirstItem() + getPageSize()}));
                }
            };
        }
        return pagination;
    }

    public String prepareList() {
        recreateModel();
        return "List";
    }

    public String prepareView() {
        current = (Propuesta) getItems().getRowData();
        selectedItemIndex = pagination.getPageFirstItem() + getItems().getRowIndex();
        return "View";
    }

    public String prepareCreate() {
        current = new Propuesta();
        selectedItemIndex = -1;
        return "Create";
    }

    public String create() {
        if (this.current.getIdea()!=null) {
            try {
                getFacade().create(current);
                JsfUtil.addSuccessMessage(ResourceBundle.getBundle("/Bundle").getString("PropuestaCreated"));
                return prepareCreate();
            } catch (Exception e) {
                JsfUtil.addErrorMessage(e, ResourceBundle.getBundle("/Bundle").getString("PersistenceErrorOccured"));
                return null;
            }
        } else {
            JsfUtil.addErrorMessage("Se requiere una Idea");
                return null;
        }
    }

    public String prepareEdit() {
        current = (Propuesta) getItems().getRowData();
        selectedItemIndex = pagination.getPageFirstItem() + getItems().getRowIndex();
        return "Edit";
    }

    public String update() {
        try {
            getFacade().edit(current);
            JsfUtil.addSuccessMessage(ResourceBundle.getBundle("/Bundle").getString("PropuestaUpdated"));
            return "View";
        } catch (Exception e) {
            JsfUtil.addErrorMessage(e, ResourceBundle.getBundle("/Bundle").getString("PersistenceErrorOccured"));
            return null;
        }
    }

    public String destroy() {
        current = (Propuesta) getItems().getRowData();
        selectedItemIndex = pagination.getPageFirstItem() + getItems().getRowIndex();
        performDestroy();
        recreateModel();
        return "List";
    }

    public String destroyAndView() {
        performDestroy();
        recreateModel();
        updateCurrentItem();
        if (selectedItemIndex >= 0) {
            return "View";
        } else {
            // all items were removed - go back to list
            recreateModel();
            return "List";
        }
    }

    private void performDestroy() {
        try {
            getFacade().remove(current);
            JsfUtil.addSuccessMessage(ResourceBundle.getBundle("/Bundle").getString("PropuestaDeleted"));
        } catch (Exception e) {
            JsfUtil.addErrorMessage(e, ResourceBundle.getBundle("/Bundle").getString("PersistenceErrorOccured"));
        }
    }

    private void updateCurrentItem() {
        int count = getFacade().count();
        if (selectedItemIndex >= count) {
            // selected index cannot be bigger than number of items:
            selectedItemIndex = count - 1;
            // go to previous page if last page disappeared:
            if (pagination.getPageFirstItem() >= count) {
                pagination.previousPage();
            }
        }
        if (selectedItemIndex >= 0) {
            current = getFacade().findRange(new int[]{selectedItemIndex, selectedItemIndex + 1}).get(0);
        }
    }

    public DataModel getItems() {
        if (items == null) {
            items = getPagination().createPageDataModel();
        }
        return items;
    }

    private void recreateModel() {
        items = null;
    }

    public String next() {
        getPagination().nextPage();
        recreateModel();
        return "List";
    }

    public String previous() {
        getPagination().previousPage();
        recreateModel();
        return "List";
    }

    public SelectItem[] getItemsAvailableSelectMany() {
        return JsfUtil.getSelectItems(ejbFacade.findAll(), false);
    }

    public SelectItem[] getItemsAvailableSelectOne() {
        return JsfUtil.getSelectItems(ejbFacade.findAll(), true);
    }

    public void eliminarParticipante(int indice) {
        this.getSelected().getParticipanteList().remove(indice);
    }

    public void eliminarImpacto(int indice) {
        this.getSelected().getImpactoList().remove(indice);
    }

    public void eliminarResultado(int indice, Integer grupo) {

        this.getSelected().getResultadoList().remove(indice);

    }

    public void eliminarResultado(Resultado resultado) {

        this.getSelected().getResultadoList().remove(resultado);

    }

    public void eliminarPresupuesto(Presupuesto presupuesto) {

        this.getSelected().getPresupuestoList().remove(presupuesto);

    }

    public void eliminarDocumento(int indice) {
        this.getSelected().getDocumentacionList().remove(indice);
    }
//    public void eliminarResultado1(int indice) {
//        System.out.print("Se inicia el borrado del resultado 1con" + indice);
//        //Resultado resultado = getResultado1().get(indice);
//        System.out.print("El resultado a borrar es " + resultado.getTiporesultado());
//        System.out.print("El tamaño antes de la lista es : " + this.getSelected().getResultadoList().size());
//        this.getSelected().getResultadoList().remove(resultado);
//        System.out.print("El tamaño despues de la lista es : " + this.getSelected().getResultadoList().size());
//    }

    public void eliminarResultado2(int indice) {
        System.out.print("Se inicia el borrado del resultado 2con" + indice);
        Resultado resultado = getResultado2().get(indice);
        System.out.print("El resultado a borrar es " + resultado.getTiporesultado());
        this.getSelected().getResultadoList().remove(resultado);
    }

    public void eliminarResultado3(int indice) {
        System.out.print("Se inicia el borrado del resultado 3 con" + indice);
        Resultado resultado = getResultado3().get(indice);
        System.out.print("El resultado a borrar es " + resultado.getTiporesultado());
        this.getSelected().getResultadoList().remove(resultado);
    }

    public List<Resultado> listaFiltrada(Gruporesultado gruporesultado) {
        List<Resultado> list = new ArrayList<Resultado>();
        if (gruporesultado != null) {
            if (this.getSelected().getResultadoList() != null) {
                for (Resultado resultado : this.getSelected().getResultadoList()) {
                    if (gruporesultado.getDescripcion().equalsIgnoreCase(resultado.getDescripcion())) {
                        list.add(resultado);
                    }
                }
            }
        }
        return list;
    }

    public Map<Integer, List<Resultado>> getResultadosMap() {

        resultadosMap = new HashMap<Integer, List<Resultado>>();
        if (this.getSelected().getResultadoList() != null) {
            for (Resultado resultado : this.getSelected().getResultadoList()) {
                List<Resultado> listaResultado = resultadosMap.get(resultado.getGruporesultado().getIdGrupoResultado());
                if (listaResultado == null) {
                    listaResultado = new ArrayList<Resultado>();
                }
                listaResultado.add(resultado);
                resultadosMap.put(resultado.getGruporesultado().getIdGrupoResultado(), listaResultado);
            }
        }
        System.out.print("Se realizo proceso de MAP");
        System.out.print("Esta vacia? " + resultadosMap.isEmpty());
        return resultadosMap;
    }

    public Map<Integer, List<Presupuesto>> getPresupuestosMap() {

        presupuestosMap = new HashMap<Integer, List<Presupuesto>>();
        if (this.getSelected().getPresupuestoList() != null) {
            for (Presupuesto presupuesto : this.getSelected().getPresupuestoList()) {
                List<Presupuesto> listaPresupuesto = presupuestosMap.get(presupuesto.getItemcosto().getIdItemCosto());
                if (listaPresupuesto == null) {
                    listaPresupuesto = new ArrayList<Presupuesto>();
                }
                listaPresupuesto.add(presupuesto);
                presupuestosMap.put(presupuesto.getItemcosto().getIdItemCosto(), listaPresupuesto);
            }
        }

        return presupuestosMap;
    }

//    public List<Presupuesto> getResultado1() {
//        List<Presupuesto> listaPresupuesto = new ArrayList<Presupuesto>();
//        System.out.print("Entrando a la lista de presupuesto ");
//        if (this.getSelected().getPresupuestoList() != null) {
//            System.out.print("Es diferente de null ");
//            for (Presupuesto presupuesto : this.getSelected().getPresupuestoList()) {
//                System.out.print("Viendo el resultado ");
//                if (presupuesto.getItemcosto() == null) {
//                    System.out.print("Grupo Resultado es null");
//                } else {
//                    System.out.print("No Grupo Resultado es null");
//                }
//                if (presupuesto.getTiporecurso().getItemcosto().getIdItemCosto() == 1) {
//                    System.out.print("Agregando el resultado ");
//                    listaPresupuesto.add(resultado);
//                }
//            }
//        } else {
//            System.out.print("la lista de resultados es null ");
//        }
//
//        return listaResultado;
//    }
    public List<Resultado> getResultado2() {
        List<Resultado> listaResultado = new ArrayList<Resultado>();
        if (this.getSelected().getResultadoList() != null) {
            for (Resultado resultado : this.getSelected().getResultadoList()) {
                if (resultado.getTiporesultado().getGruporesultado().getIdGrupoResultado() == 2) {
                    listaResultado.add(resultado);
                }
            }
        }

        return listaResultado;
    }

    public List<Resultado> getResultado3() {
        List<Resultado> listaResultado = new ArrayList<Resultado>();
        if (this.getSelected().getResultadoList() != null) {
            for (Resultado resultado : this.getSelected().getResultadoList()) {
                if (resultado.getTiporesultado().getGruporesultado().getIdGrupoResultado() == 3) {
                    listaResultado.add(resultado);
                }
            }
        }

        return listaResultado;
    }

    @FacesConverter(forClass = Propuesta.class)
    public static class PropuestaControllerConverter implements Converter {

        public Object getAsObject(FacesContext facesContext, UIComponent component, String value) {
            if (value == null || value.length() == 0) {
                return null;
            }
            PropuestaController controller = (PropuestaController) facesContext.getApplication().getELResolver().
                    getValue(facesContext.getELContext(), null, "propuestaController");
            return controller.ejbFacade.find(getKey(value));
        }

        java.lang.Integer getKey(String value) {
            java.lang.Integer key;
            key = Integer.valueOf(value);
            return key;
        }

        String getStringKey(java.lang.Integer value) {
            StringBuffer sb = new StringBuffer();
            sb.append(value);
            return sb.toString();
        }

        public String getAsString(FacesContext facesContext, UIComponent component, Object object) {
            if (object == null) {
                return null;
            }
            if (object instanceof Propuesta) {
                Propuesta o = (Propuesta) object;
                return getStringKey(o.getIdPropuesta());
            } else {
                throw new IllegalArgumentException("object " + object + " is of type " + object.getClass().getName() + "; expected type: " + PropuestaController.class.getName());
            }
        }
    }
}
